﻿
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections;

// using은 시스템정의 네임스페이스 사용하기 위함   JK


namespace PVFSLEAP
{
	class C_PVFS
	{
		F_SETT ST = new F_SETT(); // F_SETT Design 클래스의 ST 객체 생성  JK
		C_COMM CM = new C_COMM(); // C_COMM 클래스의 CM 객체 생성    JK
                

		Random K = new Random( ( int )DateTime.Now.Millisecond ); // 날짜 시간 구성   JK
		Random V = new Random( ( int )DateTime.Now.Millisecond ); // 검증 시간 구성   JK

		public static SortedList vote = new SortedList(); // 입력 값 정렬  JK



        /***************************************************************************************************
       * 1. 함수: 생성 키 만들기 위함
       * 2. 설명: 서브노드 설정값 OCHLD
       * ************************************************************************************************/
		public int generateKeys()
		{
			System.Threading.Thread.Sleep( 1 );

			int k = K.Next( 0, ST.OCHLD - 1 );
			return k;
		}


        /***************************************************************************************************
       * 1. 함수: 검증노드로 보트 유효성 검사
       * 2. 설명: 허위보고서의 허위보트 유효성을 검사하는 함수
       * 3. 입력 
       *    1) di: 분자
       *    2) d0: 분모
       * ************************************************************************************************/
		public bool checkVerifiedNode( int di, int d0 )
		{
			System.Threading.Thread.Sleep( 1 );

			int v = K.Next( 1, d0 );
            
			if ( v <= di )
				return true;
			else
				return false;
		}


        /***************************************************************************************************
      * 1. 함수: 투표값 받기
      * 2. 설명: 보고서에 작성할 투표값 받기
      * 3. 입력 
      *    1) v: 검증 투표 개수
      * ************************************************************************************************/
		public int getVote()
		{
			System.Threading.Thread.Sleep( 1 );			

			int v = V.Next( 0, ST.OCHLD - 1 );
			return v;
		}

        /***************************************************************************************************
      * 1. 함수: 검증노드 선택
      * 2. 설명: 허위투표를 검사하는 검증노드 선택
      * 3. 입력 
      *    1) chnd: 클러스터 노드 ID
      *    2) SN: 센서필드에 있는 전체 센서노드
      * ************************************************************************************************/
		public void chooseVotes( int chnd, C_NODE[] SN )
		{
			vote.Clear();

			while ( true )
			{
				int v = getVote();
				if ( SN[chnd].CPNF == true )
				{
					bool flag = false;

					for ( int c = 0; c < SN[chnd].CPND.Length; c++ )
					{
						if ( v == SN[chnd].CPND[c] )
						{
							flag = true;
							break;
						}
					}

					if ( vote.Contains( v ) == true ) 
						continue;

					if ( flag == true )
						vote.Add( v, "T" );
					else
						vote.Add( v, "F" );					
				}
				else
				{
					if ( vote.Contains( v ) == true )
						continue;

					vote.Add( v, "F" );
				}

				if ( vote.Count >= ST.OVOTE )
					break;

			}
		}

        /***************************************************************************************************
         * 1. 함수: Report 생성
         * 2. 설명: 이벤트 발생 보고서 생성
         * 3. 입력 
         *      1) chnd: 선택한 노드 (서브노드?)
         *      2) SN: 센서노드 개수 (센서노드헤드?)
         * ************************************************************************************************/
        public void generateReport( int chnd, C_NODE[] SN )
		{
			chooseVotes( chnd, SN );

			for ( int i = 0; i < SN[chnd].CPND.Length; i++ )
			{
				if ( SN[chnd].CPND[i] != 0 )
					break;
			}

			for ( int i = 0; i < ST.OVOTE; i++ )
				SN[chnd].ENGY = CM.consumeGeneratingVote( SN[chnd].ENGY, 1 );
		}
	}
}
